package ixOrm

import (
	"fmt"
	"sync"
)

// Manager 数据库管理器
type Manager struct {
	instances map[string]*Client
	mutex     sync.RWMutex
}

// GetInstanceName 获取客户端对应的实例名（优化版本）
func (m *Manager) GetInstanceName(client *Client) string {
	if client == nil {
		return "unknown"
	}

	m.mutex.RLock()
	defer m.mutex.RUnlock()

	// 优化：如果实例数量较少，直接遍历效率更高
	for name, c := range m.instances {
		if c == client {
			return name
		}
	}
	return "unknown"
}

var (
	defaultManager *Manager
	managerOnce    sync.Once
)

// GetManager 获取默认管理器实例
func GetManager() *Manager {
	managerOnce.Do(func() {
		defaultManager = NewManager()
	})
	return defaultManager
}

// NewManager 创建新的管理器
func NewManager() *Manager {
	return &Manager{
		instances: make(map[string]*Client),
	}
}

// Add 添加数据库实例
func (m *Manager) Add(name string, config *Config, options ...ConfigOption) error {
	m.mutex.Lock()
	defer m.mutex.Unlock()

	client, err := NewClient(config, options...)
	if err != nil {
		return fmt.Errorf("创建客户端失败: %w", err)
	}

	m.instances[name] = client
	return nil
}

// Get 获取数据库实例
func (m *Manager) Get(name string) (*Client, error) {
	m.mutex.RLock()
	defer m.mutex.RUnlock()

	client, exists := m.instances[name]
	if !exists {
		return nil, fmt.Errorf("实例 '%s' 不存在", name)
	}

	return client, nil
}

// Remove 移除数据库实例
func (m *Manager) Remove(name string) error {
	m.mutex.Lock()
	defer m.mutex.Unlock()

	client, exists := m.instances[name]
	if !exists {
		return fmt.Errorf("实例 '%s' 不存在", name)
	}

	// 关闭连接
	if err := client.Close(); err != nil {
		return fmt.Errorf("关闭实例失败: %w", err)
	}

	delete(m.instances, name)
	return nil
}

// List 列出所有实例名称
func (m *Manager) List() []string {
	m.mutex.RLock()
	defer m.mutex.RUnlock()

	names := make([]string, 0, len(m.instances))
	for name := range m.instances {
		names = append(names, name)
	}
	return names
}

// HealthCheck 健康检查
func (m *Manager) HealthCheck() map[string]error {
	m.mutex.RLock()
	defer m.mutex.RUnlock()

	results := make(map[string]error)
	for name, client := range m.instances {
		results[name] = client.Ping()
	}
	return results
}

// Close 关闭所有实例
func (m *Manager) Close() error {
	m.mutex.Lock()
	defer m.mutex.Unlock()

	var lastErr error
	for name, client := range m.instances {
		if err := client.Close(); err != nil {
			lastErr = fmt.Errorf("关闭实例 '%s' 失败: %w", name, err)
		}
	}

	m.instances = make(map[string]*Client)
	return lastErr
}

// 便捷方法

// AddDefault 添加默认实例
func AddDefault(config *Config, options ...ConfigOption) error {
	return GetManager().Add("default", config, options...)
}

// GetDefault 获取默认实例
func GetDefault() (*Client, error) {
	return GetManager().Get("default")
}

// Add 添加实例
func Add(name string, config *Config, options ...ConfigOption) error {
	return GetManager().Add(name, config, options...)
}

// Get 获取实例
func Get(name string) (*Client, error) {
	return GetManager().Get(name)
}

// Remove 移除实例
func Remove(name string) error {
	return GetManager().Remove(name)
}

// List 列出所有实例
func List() []string {
	return GetManager().List()
}

// HealthCheck 全局健康检查
func HealthCheck() map[string]error {
	return GetManager().HealthCheck()
}

// CloseAll 关闭所有实例
func CloseAll() error {
	return GetManager().Close()
}
